package com.beiding.workordersystem.orders.looporder.controller;

import com.beiding.workordersystem.common.dao.MPage;
import com.beiding.workordersystem.common.standard.E;
import com.beiding.workordersystem.common.standard.R;
import com.beiding.workordersystem.common.utils.*;
import com.beiding.workordersystem.main.utils.Json;
import com.beiding.workordersystem.orders.looporder.dao.CompanyItemRequiredDao;
import com.beiding.workordersystem.orders.looporder.entity.*;
import com.beiding.workordersystem.orders.looporder.model.ActiveTaxCategoriesAndCycleApply;
import com.beiding.workordersystem.orders.looporder.query.LoopOrderQuery;
import com.beiding.workordersystem.orders.looporder.query.LoopProcessQuery;
import com.beiding.workordersystem.orders.looporder.service.OrderService;
import com.beiding.workordersystem.orders.looporder.vo.*;
import com.beiding.workordersystem.system.service.UserService;
import com.beiding.workordersystem.system.service.VariableService;
import com.gitee.beiding.timer.annotation.AspectHandler;
import com.google.common.base.Joiner;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.propertyeditors.CustomDateEditor;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.WebDataBinder;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

@RestController
@RequestMapping("/loopOrder")
public class OrderController {

    @Autowired
    private OrderService orderService;


    @GetMapping("/page")
    R page(MPage page, LoopOrderQuery query) {
        return R.ok(orderService.page(page.toIPage(), query));
    }

    @GetMapping("/details")
    R details(@RequestParam String id) {
        return R.ok(orderService.details(id));
    }

    @PostMapping("/save")
    R save(@RequestBody @Validated OrderCompanyVo vo) {
        CompanyVo companyVo = vo.getCompany();
        OrderVo orderVo = vo.getOrder();
        Company company = MyBeanUtils.copy(companyVo, Company.class);
        LoopOrder order = MyBeanUtils.copy(orderVo, LoopOrder.class);
        orderService.save(company, order);
        return R.ok(order.getId());
    }

    @PostMapping("/delete")
    R delete(@RequestBody String[] ids) {
        orderService.delete(ids);
        return R.ok();
    }

    @PostMapping("/submit")
    R submit(@RequestBody String[] ids) {
        orderService.submit(ids);
        return R.ok();
    }

    @PostMapping("/pass")
    R pass(@RequestBody String[] ids) {
        orderService.pass(ids);
        return R.ok();
    }

    @PostMapping("/refuse")
    R refuse(@RequestBody @Validated RefuseVo vo) {
        orderService.refuse(vo.getIds(), vo.getReason());
        return R.ok();
    }

    @PostMapping("/start")
    R start(@RequestBody String[] ids) {
        orderService.start(ids);
        return R.ok();
    }

    @GetMapping("/task")
    R task(@RequestParam String processId) {
        return R.ok(orderService.task(processId));
    }

    @PostMapping("/designate")
    R designate(@RequestBody @Validated ProcessDesignateVo vo) {
        List<ProcessVo> processes = vo.getProcesses();
        E.isFalse(processes == null || processes.size() == 0, "未指定任何工序");
        List<LoopProcess> list = new ArrayList<>();
        for (ProcessVo process : processes) {
            LoopProcess loopProcess = MyBeanUtils.copy(process, LoopProcess.class);
            loopProcess.setPrincipalId(vo.getPrincipalId());
            loopProcess.setOrderId(vo.getOrderId());

            List<ProcessCommissionVo> commissions = process.getCommissions();
            if (commissions != null && commissions.size() > 0) {
                List<ProcessCommission> commissionList = new ArrayList<>();
                for (ProcessCommissionVo commission : commissions) {
                    ProcessCommission processCommission = new ProcessCommission();
                    BeanUtils.copyProperties(commission, processCommission);
                    commissionList.add(processCommission);
                }
                loopProcess.setCommissions(commissionList);
            }

            list.add(loopProcess);
        }
        orderService.designate(list);
        return R.ok();
    }


    @PostMapping("/accept")
    R accept(@RequestBody String[] ids) {
        orderService.accept(ids);
        return R.ok();
    }

    @PostMapping("/finish")
    R finish(@RequestBody FinishVo vo) {
        orderService.finish(vo.getIds(),vo.getSendMsg());
        return R.ok();
    }

    @GetMapping("/task/my")
    R myTask(MPage page, LoopProcessQuery query){
        return R.ok(orderService.myTask(page.toIPage(),query));
    }

    @PostMapping("/postpone")
    R postpone(@RequestBody @Validated PostPoneVo vo) {
        orderService.postpone(vo.getId(), vo.getEndTime());
        return R.ok();
    }

    @PostMapping("/endCooperation")
    R endCooperation(@RequestBody @Validated EndCooperationVo vo) {
        orderService.endCooperation(vo.getIds(),vo.getReason());
        return R.ok();
    }

    @PostMapping("/toDeal")
    R toDeal(@RequestBody String[] ids) {
        orderService.toDeal(ids);
        return R.ok();
    }

    //变量服务
    @Autowired
    private VariableService variableService;


    @AspectHandler
    public void clearToken(String id, long time) {
        variableService.set(id, null);
    }

    @PostMapping("/applyForActiveTaxCategoriesAndCycle")
    R applyFor(HttpServletRequest request, @RequestBody ActiveTaxCategoriesAndCycleApply apply) {
        apply.setApplierId(MySecurityUtils.currentCredentials().getUserId());
        String code = RandomUtils.createRandomString(20);
        variableService.set(code, Json.stringify(apply));
        ApplicationUtils.get(this).clearToken(code, 1000 * 3600 * 24);
        return R.ok();//uuNrSWSl1MyKdkMOR2Sg
    }

    @Autowired
    private UserService userService;

    @GetMapping("/atcc.html")
    R controller(HttpServletResponse response, String code) throws IOException {
        String value = variableService.getValue(code);
        E.notNull(value, "链接不存在或已失效");
        response.setContentType("text/html;charset=UTF-8");
        ActiveTaxCategoriesAndCycleApply parse = Json.parse(value, ActiveTaxCategoriesAndCycleApply.class);

        String name = userService.getById(parse.getApplierId()).getName();
        String act = Joiner.on(",").join(parse.getTaxCategoriesAndCycles());
        String orderId = parse.getOrderId();

        String string = ResourceUtils.classPathResourceAsString("activeTc.html");

        string = string.replace("${name}", name).replace("${orderDetailsUrl}", "http://www.baidu.com").replace("${orderId}", orderId).replace("${activeTC}", act).replace("${passActiveUri}", "/loopOrder/passApplyForActiveTaxCategoriesAndCycle/" + code);

        response.getWriter().write(string);

        return null;
    }

    @GetMapping("/passApplyForActiveTaxCategoriesAndCycle/{code}")
    R passApplyForActiveTaxCategoriesAndCycle(@PathVariable String code) {

        //获取code
        String value = variableService.getValue(code);
        if (value == null) {
            E.error("令牌不存在或已失效");

        }
        ActiveTaxCategoriesAndCycleApply parse = Json.parse(value, ActiveTaxCategoriesAndCycleApply.class);
        orderService.activeTaxCategoriesAndCycle(parse.getOrderId(), parse.getTaxCategoriesAndCycles());

        variableService.set(code, null);

        return R.ok("申请处理成功");
    }


    @Autowired
    private CompanyItemRequiredDao companyItemRequiredDao;

    @PostMapping("/settings/save")
    R saveSettings(@RequestBody CompanyItemRequired required) {
        required.setId("0");
        companyItemRequiredDao.updateById(required);
        return R.ok();
    }

    @GetMapping("/settings/get")
    R getSettings(){
        return R.ok(companyItemRequiredDao.selectById("0"));
    }

    @InitBinder
    public void initBinder(WebDataBinder binder) {
        SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");
        dateFormat.setLenient(false);
        binder.registerCustomEditor(Date.class, new CustomDateEditor(dateFormat, true));
    }

}
